import React, {Component} from 'react';
import ReactDOM from 'react-dom';

interface Props {
  render: (value: State) => React.ReactNode
}

interface State {
  x: number;
  y: number;
}

type PropsFromState = State;

/** https://reactjs.org/docs/render-props.html#be-careful-when-using-render-props-with-reactpurecomponent
A component with a render prop takes a function that returns a React element and calls it instead of implementing its own render logic.

Libraries that use render props include React Router, Downshift and Formik.


*/

/*class MouseTracker extends Component<Props, State> {
  constructor(props: Props) {
    super(props);
    this.state = {x: 0, y: 0}
  }

  handleMouseMove = (event: React.MouseEvent) => {
    this.setState({
      x: event.clientX
      , y: event.clientY
    })
  };

  render() {
    return (
      <div onMouseMove={this.handleMouseMove} style={{border: '1px solid red'}}>
        {this.props.render(this.state)}
      </div>
    );
  }
}

ReactDOM.render(<MouseTracker render={
    (value:State)=>(
        <div>
            <p>请现在移动鼠标</p>
            <p>当前鼠标的位置x:{value.x},y:{value.y}</p>
        </div>
    )
}/>, document.getElementById('root'));*/



//也可结合高阶组件
class MouseTracker extends Component<Props, State> {
  constructor(props: Props) {
    super(props);
    this.state = {x: 0, y: 0}
  }

  handleMouseMove = (event: React.MouseEvent) => {
    this.setState({
      x: event.clientX
      , y: event.clientY
    })
  };

  render() {
    return (
      <div onMouseMove={this.handleMouseMove} style={{border: '1px solid red'}}>
        {this.props.render(this.state)}
      </div>
    );
  }
}
const MyComponent = (value: State) => (
  <div>
    <p>请现在移动鼠标</p>
    <p>当前鼠标的位置x:{value.x},y:{value.y}</p>
  </div>
);

function withMouseTracker(OldComponent: React.FC<State>) {
  return (props: {}) => {
    return (
      <MouseTracker render={mouseProps => <OldComponent {...props} {...mouseProps}/>}/>
    )
  };
}

const X = withMouseTracker(MyComponent);

ReactDOM.render(<MouseTracker render={X}/>, document.getElementById('root'));
